import 'dart:convert';
import 'dart:developer';

import 'package:lib_common/lib_common.dart';
import 'package:lib_http/lib_http.dart';

import 'body_config_page.dart';
import 'headers_config_page.dart';
import 'http_config_page.dart';
import 'params_config_page.dart';

class HttpRequestPage extends StatefulWidget {
  const HttpRequestPage({super.key});

  @override
  State<HttpRequestPage> createState() => _HttpRequestPageState();
}

class _HttpRequestPageState extends State<HttpRequestPage> {
  List<String> supportMethods = [HttpManager.getMethod, HttpManager.postMethod];

  String requestMethod = HttpManager.getMethod;
  TextEditingController urlController = TextEditingController();

  Map<String, dynamic>? headers;
  Map<String, dynamic>? params;
  dynamic data;

  String resultText = "";

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        backgroundColor: Colors.white,
        appBar: AppBar(
            backgroundColor: Colors.white,
            elevation: 1.0,
            shadowColor: Colors.black26,
            centerTitle: true,
            actions: [_buildSettingAction()],
            title: const Text("Http Request", style: TextStyle(color: Colors.black87, fontSize: 18.0, fontWeight: FontWeight.w500))),
        body: ListView(children: [
          _buildTop(),
          _buildRequestHeader(),
          _buildRequestParams(),
          _buildBodyParams(),
          _buildRequestButton(),
          _buildResultBody()
        ]));
  }

  Widget _buildSettingAction() {
    return GestureDetector(
        child: Container(width: kToolbarHeight, color: Colors.transparent, child: const Icon(Icons.settings_outlined, color: Colors.blue)),
        onTap: () {
          FocusScope.of(context).requestFocus(FocusNode());
          Navigator.push(context, MaterialPageRoute(builder: (context) => const HttpConfigPage()));
        });
  }

  Widget _buildTop() {
    return Container(
        height: 48.0,
        margin: const EdgeInsets.symmetric(vertical: 6.0, horizontal: 8.0),
        decoration: BoxDecoration(color: Colors.black.withOpacity(0.05), borderRadius: BorderRadius.circular(4.0)),
        child: Row(children: [
          GestureDetector(
              child: Container(
                  color: Colors.transparent,
                  padding: const EdgeInsets.symmetric(horizontal: 16.0),
                  child: Row(children: [
                    Text(requestMethod, style: const TextStyle(fontWeight: FontWeight.bold)),
                    const Icon(Icons.keyboard_arrow_down)
                  ])),
              onTap: () => _chooseRequestMethod()),
          Container(width: 1.0, height: 20.0, color: Colors.black12),
          Expanded(
              child: TextField(
                  controller: urlController,
                  decoration: const InputDecoration(
                      hintText: "请输入url", border: InputBorder.none, contentPadding: EdgeInsets.symmetric(horizontal: 10.0))))
        ]));
  }

  Widget _buildRequestHeader() {
    return GestureDetector(
        child: Container(
            height: 48.0,
            alignment: Alignment.center,
            margin: const EdgeInsets.symmetric(horizontal: 10.0, vertical: 5.0),
            decoration: BoxDecoration(
                color: Colors.white,
                borderRadius: BorderRadius.circular(4.0),
                boxShadow: const [BoxShadow(blurRadius: 1.0, color: Colors.black26)]),
            child: const Text("Headers Config", style: TextStyle(fontWeight: FontWeight.w500, fontSize: 16.0))),
        onTap: () {
          FocusScope.of(context).requestFocus(FocusNode());
          Navigator.push(context, MaterialPageRoute(builder: (context) => HeadersConfigPage(headers))).then((value) {
            if (value is Map<String, dynamic>) {
              headers = value;
            }
          });
        });
  }

  Widget _buildRequestParams() {
    return GestureDetector(
        child: Container(
            height: 48.0,
            alignment: Alignment.center,
            margin: const EdgeInsets.symmetric(horizontal: 10.0, vertical: 5.0),
            decoration: BoxDecoration(
                color: Colors.white,
                borderRadius: BorderRadius.circular(4.0),
                boxShadow: const [BoxShadow(blurRadius: 1.0, color: Colors.black26)]),
            child: const Text("Params Config", style: TextStyle(fontWeight: FontWeight.w500, fontSize: 16.0))),
        onTap: () {
          FocusScope.of(context).requestFocus(FocusNode());
          Navigator.push(context, MaterialPageRoute(builder: (context) => ParamsConfigPage(params))).then((value) {
            if (value is Map<String, dynamic>) {
              params = value;
            }
          });
        });
  }

  Widget _buildBodyParams() {
    return GestureDetector(
        child: Container(
            height: 48.0,
            alignment: Alignment.center,
            margin: const EdgeInsets.symmetric(horizontal: 10.0, vertical: 5.0),
            decoration: BoxDecoration(
                color: Colors.white,
                borderRadius: BorderRadius.circular(4.0),
                boxShadow: const [BoxShadow(blurRadius: 1.0, color: Colors.black26)]),
            child: const Text("Body Config", style: TextStyle(fontWeight: FontWeight.w500, fontSize: 16.0))),
        onTap: () {
          FocusScope.of(context).requestFocus(FocusNode());
          Navigator.push(context, MaterialPageRoute(builder: (context) => BodyConfigPage(data))).then((value) {
            data = value;
          });
        });
  }

  Widget _buildRequestButton() {
    return GestureDetector(
        child: Container(
            height: 48.0,
            alignment: Alignment.center,
            margin: const EdgeInsets.symmetric(horizontal: 10.0, vertical: 5.0),
            decoration: BoxDecoration(color: Colors.blue, borderRadius: BorderRadius.circular(4.0)),
            child: const Text("Send", style: TextStyle(fontWeight: FontWeight.w500, fontSize: 16.0, color: Colors.white))),
        onTap: () {
          _doRequest();
        });
  }

  Widget _buildResultBody() {
    return Container(
        margin: const EdgeInsets.all(10.0),
        padding: const EdgeInsets.all(10.0),
        decoration: BoxDecoration(
            color: resultText.isEmpty ? Colors.transparent : Colors.black.withOpacity(0.05), borderRadius: BorderRadius.circular(4.0)),
        child: Text(resultText));
  }

  void _chooseRequestMethod() {
    FocusScope.of(context).requestFocus(FocusNode());
    showModalBottomSheet(
            context: context,
            builder: (context) {
              var methodList = supportMethods
                  .map((method) => GestureDetector(
                      child: Container(
                          height: 48.0,
                          alignment: Alignment.center,
                          margin: const EdgeInsets.symmetric(horizontal: 10.0, vertical: 5.0),
                          decoration: BoxDecoration(color: Colors.white, borderRadius: BorderRadius.circular(4.0)),
                          child: Text(method, style: const TextStyle(fontWeight: FontWeight.w500, fontSize: 16.0))),
                      onTap: () {
                        Navigator.pop(context, method);
                      }))
                  .toList();
              methodList.add(GestureDetector(
                  child: Container(
                      height: 48.0,
                      alignment: Alignment.center,
                      margin: const EdgeInsets.only(left: 10.0, right: 10.0, bottom: 16.0, top: 5.0),
                      decoration: BoxDecoration(color: Colors.white, borderRadius: BorderRadius.circular(4.0)),
                      child: const Text("Cancel", style: TextStyle(fontWeight: FontWeight.w500, fontSize: 16.0, color: Colors.black45))),
                  onTap: () {
                    Navigator.pop(context);
                  }));
              return Column(mainAxisSize: MainAxisSize.min, children: methodList);
            },
            backgroundColor: Colors.transparent,
            barrierColor: Colors.black.withOpacity(0.05))
        .then((value) {
      if (value is String) {
        requestMethod = value;
        setState(() {});
      }
    });
  }

  void _doRequest() {
    switch (requestMethod) {
      case HttpManager.getMethod:
        _doGetRequest();
        break;
      case HttpManager.postMethod:
        LogUtils.v("_doPostRequest:$data");
        if (data is Map<String, dynamic>) {
          _doPostRequest();
        } else if (data is FormData) {
          _doUploadRequest();
        } else {
          SmartDialog.showToast("请求参数有误:$data");
        }
        break;
    }
  }

  void _doGetRequest() {
    String url = urlController.text;
    HttpManager.getInstance().get(url, options: Options(headers: headers), params: params, startCallback: () {
      log("开始执行请求");
    }, successCallback: (result) {
      log("执行请求成功，结果类型:${result.runtimeType}");
      if (result != null) {
        resultText = json.encode(result);
        setState(() {});
      }
    }, errorCallback: (error) {
      log("执行请求失败，错误信息:$error");
    }, finishCallback: () {
      log("执行请求完成");
    });
  }

  void _doPostRequest() {
    String url = urlController.text;
    HttpManager.getInstance().post(url, options: Options(headers: headers), params: params, data: data, startCallback: () {
      log("开始执行请求");
    }, successCallback: (result) {
      log("执行请求成功，结果类型:${result.runtimeType}");
      if (result != null) {
        resultText = json.encode(result);
        setState(() {});
      }
    }, errorCallback: (error) {
      log("执行请求失败，错误信息:$error");
    }, finishCallback: () {
      log("执行请求完成");
    });
  }

  void _doUploadRequest() {
    String url = urlController.text;
    HttpManager.getInstance().upload(url, options: Options(headers: headers), params: params, data: data, onSendProgress: (count, total) {
      log("上传文件进度:$count，文件总大小:$total");
    }, successCallback: (result) {
      log("执行请求成功，结果类型:${result.runtimeType}");
      if (result != null) {
        resultText = json.encode(result);
        setState(() {});
      }
    }, errorCallback: (error) {
      log("执行请求失败，错误信息:$error");
    });
  }
}
